function vue(options){
    this.data = options.data
    var id = options.el

    observe(this.data,this)
    var dom = nodeToFragment(document.getElementById(id), this)
    document.getElementById(id).appendChild(dom);
}

function nodeToFragment(node,vm){
    var flag = document.createDocumentFragment();
    var child

    while(child = node.firstChild){
        compiler(child, vm);
        flag.appendChild(child);
    }
    return flag;
}

function compiler(node,vm){
    var reg = /{{(.*)}}/;

    if(node.nodeType === 1){
        var attr = node.attributes;
        for (var i = 0; i < attr.length; i++) {
            if (attr[i].nodeName == 'v-model') {
                var name = attr[i].nodeValue; // 获取v-model绑定的属性名
                node.addEventListener('input',(e)=>{
                    vm[name] = e.target.value
                })
                node.value = vm.data[name]; // 将data的值赋值给该node
                node.removeAttribute('v-model');
            }
        }
    }

    if(node.nodeType === 3){
        console.log(node.nodeValue);
        if(reg.test(node.nodeValue)){
            var name = RegExp.$1; // 获取匹配到的字符串
            name = name.trim();
            console.log(name);
            new Watcher(vm, node, name);
            // node.nodeValue = vm.data[name]; // 将data的值赋值给该node
        }
    }
}

function observe(obj,vm){
    Object.keys(obj).forEach((key)=>{
        defineReactive(vm,key,obj[key])
    })
}

function defineReactive(obj, key, val){
    var dep = new Dep() 
    Object.defineProperty(obj,key,{
        get(){
            if (Dep.target) {
                dep.addSub(Dep.target);
            }
            return val
        },
        set(newVal){
            if (newVal === val) {
                return; 
            } else {
                val = newVal;
                dep.notify()        
                console.log(val); // 方便看效果
            }
        }
    })
}

function Watcher (vm, node, name){
    Dep.target = this
    this.name = name;
    this.node = node;
    this.vm = vm;
    this.update();
    Dep.target = null;
}
    Watcher.prototype = {
        update: function () {
            this.get();
            this.node.nodeValue = this.value;
        },

        // 获取data中的属性值
        get: function () {
            this.value = this.vm[this.name]; // 触发相应属性的get
        }
    }

function Dep(){
    this.subs = []
}
Dep.prototype = {
    addSub: function (sub) {
        this.subs.push(sub);
    },

    notify: function () {
        this.subs.forEach(function (sub) {
            sub.update();
        });
    }
}

export default vue
